﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using PalFramework.Object;
using PalBattleEmulator.Command;

namespace PalBattleEmulator.Graphic
{
    public class CharacterGraphic : UnitGraphic
    {
        private const int STATE_INDEX_NORMAL = 0;
        private const int STATE_INDEX_DANGER = 1;
        private const int STATE_INDEX_AGONAL = 2;
        private const int STATE_INDEX_DEFENCE = 3;
        private const int STATE_INDEX_BEHIT = 4;
        private const int STATE_INDEX_CAST_PREPARE = 5;
        private const int STATE_INDEX_CAST_FINISH = 6;
        private const int STATE_INDEX_ATTACK_PREPARE = 7;
        private const int STATE_INDEX_ATTACK_PROCESS = 8;
        private const int STATE_INDEX_ATTACK_FINISH = 9;
        private const int STATE_INDEX_STEAL = 10;

        public const int LAST_TIMES_MAX = 99;
        private const int ATTACK_PREPARE_LAST_TIMES = 2;
        private const int ATTACK_PROCESS_LAST_TIMES = 2;
        private const int ATTACK_FINISH_LAST_TIMES = 4;

        private ICharacter character;
        private GraphicFrame frame;

        private CharacterGraphicState state;

        public CharacterGraphicState State
        {
            get { return state; }
            set
            {
                state = value;
                switch (state)
                {
                    case CharacterGraphicState.Normal:
                        frame.FrameIndex = STATE_INDEX_NORMAL;
                        break;
                    case CharacterGraphicState.Danger:
                        frame.FrameIndex = STATE_INDEX_DANGER;
                        break;
                    case CharacterGraphicState.Agonal:
                        frame.FrameIndex = STATE_INDEX_AGONAL;
                        break;
                }
            }
        }

        public int DefaultPosX
        {
            get
            {
                return character.Array.PosX;
            }
        }

        public int DefaultPosY
        {
            get
            {
                return character.Array.PosY;
            }
        }

        public void Initialize(ICharacter character)
        {
            this.character = character;

            //填充source
            sources = new List<BitmapSource>();
            string imageIndex = character.Sprite;
            for (int i = 0; ; i++)
            {
                BitmapSource img = (BitmapSource)ContextModules.CharacterImageManager.GetImage(imageIndex, i);
                if (img == null) break;
                sources.Add(img);
            }

            //初始化frame

            frame = new GraphicFrame();
            State = CharacterGraphicState.Normal;
            frame.RepeatTimes = LAST_TIMES_MAX;
            frame.PosX = DefaultPosX;
            frame.PoxY = DefaultPosY;
            frame.ZIndex = ZINDEX_NORMAL;

            
        }

        public override GraphicFrame GetIdleFrame()
        {
            return frame;
        }

        public override void OnCommand(GameCommand command)
        {
            switch (command.Type)
            {
                case CommandTypes.GRAPHIC_ATTACK_BEGIN:
                    AttackGraphicCommand attackCommand = (AttackGraphicCommand)command;

                    //frames
                    GraphicFrame frame;

                    frame = new GraphicFrame();
                    frame.FrameIndex = STATE_INDEX_ATTACK_PREPARE;
                    frame.RepeatTimes = ATTACK_PREPARE_LAST_TIMES;
                    frame.PosX = DefaultPosX;
                    frame.PoxY = DefaultPosY;
                    frame.ZIndex = ZINDEX_ACTIVE;
                    this.actionFrames.Enqueue(frame);

                    frame = new GraphicFrame();
                    frame.FrameIndex = STATE_INDEX_ATTACK_PROCESS;
                    frame.RepeatTimes = ATTACK_PROCESS_LAST_TIMES;
                    frame.PosX = attackCommand.PosX + 30;
                    frame.PoxY = attackCommand.PosY + 30;
                    frame.ZIndex = ZINDEX_ACTIVE;
                    this.actionFrames.Enqueue(frame);

                    frame = new GraphicFrame();
                    frame.FrameIndex = STATE_INDEX_ATTACK_FINISH;
                    frame.RepeatTimes = ATTACK_FINISH_LAST_TIMES;
                    frame.PosX = attackCommand.PosX + 30;
                    frame.PoxY = attackCommand.PosY + 30;
                    frame.ZIndex = ZINDEX_ACTIVE;
                    this.actionFrames.Enqueue(frame);
                    break;
            }
        }
    }

    

    public enum CharacterGraphicState
    {
        Normal,
        Danger,
        Agonal
    }
}
